﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml.Linq;
using System.Windows.Forms;
using IrisGenerator.Common.Tools;
using System.Reflection;


namespace IrisGenerator.Common.UI.XmlConfiguration
{
    internal class XmlDatagridConfiguration:XmlConfiguration
    {
        public override void LoadConfiguration(XElement rootElement,Control ctrl)
        {
            if (rootElement == null || ctrl == null)
                return;

            DataGridView grid = ctrl as DataGridView;
            if (grid == null)
                throw new ApplicationException("The control " + ctrl.Name + " is not a datagrid. Configuration data can not be loaded");

            FillObjectFromXml(rootElement, grid);

            XElement columnsNode = XmlLinq.LoadSingleDescendantNode(rootElement, "Columns");

            LoadColumns(columnsNode, grid);
        }

        private void LoadColumns(XElement columnsNode, DataGridView grid)
        {
            if (columnsNode == null)
                return;

            var dbQuery = from node in columnsNode.Descendants()
                          select node;

            foreach (var columnNode in dbQuery)
            {
                LoadColumn(columnNode, grid);
            }
        }

        private void LoadColumn(XElement columnNode, DataGridView grid)
        {
            if (columnNode == null || grid == null)
                return;

            string columnType = columnNode.Name.LocalName;
            
            switch (columnType)
            {
                case "TextColumn":
                    AddTextColumn(columnNode, grid);
                    break;
                case "BoolColumn":
                    AddBoolColumn(columnNode, grid);
                    break;
                default:
                    throw new ApplicationException("The column type " + columnType + " is not a valid column type.");

                    break;
            }

        }

        private void AddTextColumn(XElement textColumnNode, DataGridView grid)
        {
            DataGridViewTextBoxColumn column = new DataGridViewTextBoxColumn();
            grid.Columns.Add(column);
            FillObjectFromXml(textColumnNode, column);
        }

        private void AddBoolColumn(XElement boolColumnNode, DataGridView grid)
        {
            DataGridViewCheckBoxColumn column = new DataGridViewCheckBoxColumn();
            grid.Columns.Add(column);
            FillObjectFromXml(boolColumnNode, column);
        }

        private void FillObjectFromXml(XElement node, object objectToFill)
        {
            if (node == null || objectToFill == null)
                return;

            IEnumerable<XAttribute> attributes = node.Attributes();
            if (attributes == null)
                return;

            foreach (XAttribute att in attributes)
            {
                FillObjectProperty(att, objectToFill);    
            }
        }

        private void FillObjectProperty(XAttribute xmlAttribute,object objectToFill)
        {

            if (xmlAttribute == null || objectToFill == null)
                return;

            Type objType = objectToFill.GetType();
            PropertyInfo property = objType.GetProperty(xmlAttribute.Name.LocalName);

            if (property == null)
                return;

            Type objectType=property.PropertyType;

            if (objectType==null)
                return;

            object value = Convert.ChangeType(xmlAttribute.Value, objectType);

            property.SetValue(objectToFill, value, null);
            
        }

    }
}
